fix: exempt the half-state patrol's anchor from the stale bot - #15016
Merged
Conversation
Add `tracking` to `exempt-issue-labels` in `.github/workflows/stale.yml` with a comment explaining why: the patrol's anchor issue carries `tracking` as its only label and stays alive solely through the patrol's own heartbeat, so without this exemption a dead patrol's anchor is marked stale at 60 days and closed 14 days later -- removing the one artifact whose job is to make that death visible. Co-Authored-By: Claude Fable 5.1 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_019RfFHiRCSs3JXLK4cwcfox
os-steve
marked this pull request as ready for review
September 3, 2026 17:59
os-steve
enabled auto-merge
September 3, 2026 17:59
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Fixes #15002
.github/workflows/stale.yml'sexempt-issue-labelslist did not includetracking, the only label the half-state patrol's anchor issue (#9857, confirmed againsthalf-state-patrol.yml's own header) carries — so an anchor whose sole protection is the patrol's own heartbeat (its periodic body rewrite) would gostaleat 60 days and close 14 days after that once the patrol stopped running, deleting the one artifact whose job is to make that death visible. This PR addstrackingto theexempt-issue-labelsvalue (now'pinned,security,roadmap,tracking') and a comment line above it recording the reason, touching no other key and no other file (exempt-pr-labelsis unchanged). The hotcrm copy of this workflow is out of scope here per the triage comment — it belongs to therepo:hotcrmseam card.Premises verified on
origin/mainbefore editing:exempt-issue-labels: 'pinned,security,roadmap'is at.github/workflows/stale.yml:48atorigin/main33681eae— confirmed on the branch (still:48at commitee370d31, the branch's fork point).trackingand onlytracking, by design:half-state-patrol.ymllines 166-167 — "The anchor deliberately carriestrackingand NOdomain:*label:trackingis in the sweeper's own H13_EXEMPT_LABELS...".actions/stale@v11.0.0; itsaction.ymldocumentsexempt-issue-labels(exact spelling) as "The labels that mean an issue is exempt from being marked stale. Separate multiple labels with commas."python3 -c 'import yaml,sys; yaml.safe_load(open(".github/workflows/stale.yml"))'parses clean after the edit.node scripts/pm/check-governed-merges.mjs --test .github/workflows/stale.yml→ NOT governed (0 of 1 path hits the register) — ordinary queue landing applies.Gate table — verification run at head
06e82410e4141b425b4cc3cdb5893de0fc2eed6c(re-derived withnode scripts/pm/dispatch-gates.mjs --repo objectstack-ai/objectstack --commands .github/workflows/stale.yml, which reproduced exactly this 26-command list, no additions):check-aggregator-roster.mjs✓ check-aggregator-roster: 3 aggregator(s) across 2 workflow(s); roster == needs: in both directions, and all 3 required-context aggregate(s) declared.check-closing-keyword-parity.mjscheck-closing-keyword-parity: OK (3 parsers agree on all 9 keywords and both measured separators; sweep found 5 file(s) carrying the grammar across 8175 tracked file(s), all registered).check-comment-mask-corpus.mjs✓ comment-mask corpus sweep [scripts/js-comment-mask.mjs]: 5832 files, 0 disagree, 0 unparseable, 47.9s (comparator self-test: 12 cases pass).check-position-name-fold-loaders.mjs✓ check-position-name-fold-loaders: ... 4 reference(s): 2 test, 2 declared instrument, 0 loader.(materialisation worklist stays EMPTY)check-required-contexts.mjsci.ymljobs to all 4 required-context names (Test Core,Dogfood Regression Gate,Build Core,Temporal Conformance (live PG + MySQL)), exit 0check-self-test-wired.mjs✓ check-self-test-wired: every one of the 166 script(s) CI runs that ship a --self-test has that self-test run by CI.check-self-test-workflow-commands.mjs✓ check-self-test-workflow-commands: no self-test CI runs prints a line the Actions runner would parse as a workflow command.check-shard-attestation.mjs✓ check-shard-attestation: 2 aggregate gate(s) count 3 declared leg(s) across 3 attesting job(s).check-step-collectors.mjs✓ check-step-collectors: 394 run: steps across 30 workflow(s); 4 step(s) run 2+ independent self-tests, all of them through a collector.check-whole-set-label-write.mjsuses:pin(s) judged and cleared, exit 0docs-audit/check-drift-comment.mjs✓ check-drift-comment: 56 cases pass across 5 fixture diff(s).pm/ci-failure.mjs --self-testcheck:agent-test-spelling--self-test, exit 0check:declared-population-live✓ check:declared-population-live — 159 of 204 famil(ies) declare a path population, and every one of them reaches this tree's 8175 tracked file(s).check:node-versioncheck-node-version: OK (35 setup-node step(s) across 30 workflow(s), all on Node 22).check:nul-bytescheck-nul-bytes: OK (scanned 8168 text file(s) ... no raw ASCII control bytes).check:pm-dispatch-gates✓ dispatch-gates self-test: 1288 cases pass.check:pnpm-acquisitioncheck:pnpm-filter-targets✓ check:pnpm-filter-targets: 142/181 --filter occurrence(s) across 33 file(s) resolve against 79 workspace package(s); ...check:refd-timer-probeOK check-refd-timer-probe: 5827 source file(s) swept; the process-global timer probe is read ... and nowhere else.check:required-contextscheck:shard-attestation✓ check-shard-attestation: 2 aggregate gate(s) count 3 declared leg(s) across 3 attesting job(s).check:stall-guard-budgetcheck-stall-guard-budget: OK (30 workflow file(s), 53 job(s), 578 step(s), 7 guard-wrapped step(s); every effective cap clears its job budget by at least one stall window).check:stall-guard-headroommeasure-stall-guard-headroom --self-test: 35 assertion(s) passed.check:watch-hint-literal✓ check-watch-hint-literal: 48 declaration(s) across 4 rostered name(s) ... no unrostered spelling of the idiom in the tree.check:workflow-status-functionscheck-workflow-status-functions: OK (scanned 30 workflow file(s), 53 job(s), 26 job-level if: expression(s); 10 read needs.*.outputs.*, all naming a status function).All 26/26 exit 0. First attempt (before
pnpm installhad been run in this worktree) surfaced the gate scripts' ownPREREQUISITE NOT MET(exit 3) declarations plus one rawERR_MODULE_NOT_FOUND— none of those were red gates, they were NOT MEASURED; the table above is the post-install re-run.skip-changeset: nothing published from any package (workflow-only diff) — label applied additively and read back.Generated by Claude Code